One control opens the account menu on every RoomPlans surface: an avatar with a chevron, no plate and no border. The header cluster runs messages → notifications → account, so the mark carrying a count sits furthest from the account it belongs to and closest to the content it refers to. Desktop opens a dropdown anchored to the avatar; mobile opens a bottom sheet. Click anything on this page — every specimen is live.
Trigger · avatar + chevronOpen state · ink ring + 180° flipMotion · 160ms colour / 240ms transform
01 · Anatomy
The trigger
Two marks, 6px apart, on no background — 38px on every surface, desktop and mobile alike. The avatar carries the initial in flame on a warm tint; the chevron matches the header glyphs' stroke and size so the cluster reads as one type family.
Rest
L
Avatar 38px in a 48px target · chevron 26px in --ink-900, heavier stroke for visibility · gap 6px · no border, no fill behind
Hover
L
A sunken-tint wash appears behind both marks. Desktop only — mobile has no hover state.
Open
L
2px ink ring on the avatar, chevron flipped 180°. Both states persist while the menu is open.
02 · Desktop
Dropdown
Header: 52px search field with an 18px glyph in a 38px flame circle, a 38px avatar in a 48px target, 28px between the three marks and a 64px page gutter. The panel is 272px, right-aligned to the trigger, 8px below it — three captioned groups (Your work · Discover · Account), no hairlines. Hover is an inset rounded wash. Click the avatar to open, then any row to select — the row washes and the selection is echoed beneath.
Right-align the panel to the trigger, 8px clear of it.Group with 10px uppercase captions in --text-faint, not hairlines — three groups, and the panel carries no rules at all.Mark unread with a 7px flame dot; mark the current choice with a flame tick.Rows are 38px with an inset rounded hover wash, 8px in from the panel edge — the same treatment cards already use.
Don't
Don't put a border or a filled pill around the trigger.Don't use flame for row text, icons or hover — flame marks status only.Don't exceed one accent per row, add a second chevron inside the panel, or reintroduce dividers between groups — the captions do that work.Don't centre the panel or let it overhang the viewport edge.
03 · Mobile
Bottom sheet
Same trigger, different surface. The sheet rises over a scrim with a grab handle and 46px rows — thumb-reachable, and it never duplicates the destinations the tab bar already carries.
A 250px panel pinned to a top-right avatar is out of thumb reach on a 390pt screen; the sheet puts every row in the lower half.The sheet carries only what the tab bar cannot — account, language, support, role switch, log out. My Projects, Explore, Add Project and Messages stay in the tabs.The Settings tab and the avatar open the same sheet, so there is one destination and two ways in.Dismiss on scrim, handle, ✕ or a row tap. Confirmations appear above the sheet, never inside it.
Selecting a language
1. The language row shows the current locale as its label — never the word "Language" — with a right chevron marking it as a submenu.2. Tapping it replaces the menu body in place: a back row titled "Language", then the locale list. The panel does not stack a second floating layer.3. No tick in the list: each locale is written in its own language, and the menu row already shows the active one.4. Picking one applies immediately, returns to the main menu and updates the row label. The back arrow leaves the locale unchanged.
Spec
Panel width 250px desktop · full width mobileRow height 40px · 46pxRadius card · frame top cornersElevation shadow-float, no borderScrim rgba(20,14,10,.5) mobile only
04 · Cross-role rows
Sign up, or switch
The two rows below the divider look alike but do opposite things, and which one a person sees depends on whether they already hold that role. The glyph is what tells them apart — never the label alone.
Homeowner who is also a designer — one resolved row per role
Reading this panel
Mixed rows are normal. This person has a designer account but no supplier account, so one row switches and one still signs up. Resolve each row independently — the state is per role, not per menu.The switch row carries no special treatment beyond the same --surface-sunken wash every other row uses. It gets no flame, no fill, no border — a switch is navigation, not a primary action.The role line still says Homeowner. It names the workspace you are in now, so after switching it reads “Designer” and this row becomes “Switch to homeowner”.Order is fixed: switches sit above signups, because a row that changes your workspace is used far more often than one that opens a marketing page.
No account in that role
For designers
Goes to the designer signup page. This is marketing wayfinding for someone in the wrong account — not an action a homeowner takes.
For material suppliers
Goes to the supplier signup page.
Label keeps the marketing phrasing — “For …” — and the trailing 14px arrowRight reads as “leaves this menu”.
Already holds that role
Switch to designer
Changes the active workspace. Same person, same login — the menu, tab bar and every destination reload in the designer product.
Switch to supplier
Changes the active workspace to the supplier product.
Label becomes “Switch to …” and the trailing glyph becomes arrowsLeftRight — two arrows passing, which reads as exchange rather than departure. It stays on the right so both row types share one label column; shape and wording already tell them apart, and a leading glyph would pull the row back into the account block it was demoted out of.
Do
Resolve the row per account at render time — never show both a signup and a switch for the same role.Name the destination in the singular: “Switch to designer”, not “Switch to designers”.Keep both variants at --fs-body-s (14px) below the divider, 40px desktop / 46px mobile, glyph trailing. The ladder is 16px account rows → 14px cross-role → 13px Log out.Switching is instant and reversible: the same row in the other product reads “Switch to homeowner”.
Don't
Don't use “For designers” for an account that already has one — it sends an existing PRO to a signup form.Don't use arrowRight for a switch, or arrowsLeftRight for a signup. The glyph is the only reliable signal.Don't promote a switch into the main block — it belongs below the divider even when the person uses it daily.Don't confirm a switch with a dialog; it destroys nothing and is one tap to reverse.
05 · Signed out
Before an account exists
A first-time visitor gets the same control and the same surface, with the account rows removed. Nothing here asks them to sign up before they have seen a render — the free path stays open and Log in is an offer, not a wall.
Signed out — desktop dropdown
For Homeowner
Sign up or sign in
Discover
ExploreAdd Project
Help
Help and supportEnglish
For designers
For material suppliers
What changes, and why
“For Homeowner” is the title here, not a caption. Signed in it is a 12px qualifier under a name; signed out there is no name, so it becomes the heading that says which product you are looking at — 20px display, the one place the phrase keeps its “For”.One filled control, covering both cases. A visitor rarely knows or cares whether they already have an account, so a single “Sign up or sign in” avoids making them choose — the screen behind it branches on the email. Two side-by-side buttons would split one action into a decision.Four rows survive, and they are the ones that work logged out. Explore and Add Project are the free path; Help and Language are utilities. My Projects, Messages, Favorites, Settings and Log out all require an account, so they are removed rather than shown disabled.Cross-role rows never switch here. With no account there is no role to switch to, so both keep the signup label and the single arrowRight.
Do
Keep the trigger identical — avatar circle with a neutral glyph in place of an initial, same chevron, same 44px target.Return the visitor to where they were after login; never dump them on the dashboard.Same sheet on mobile, same rows, 46px tall.
Don't
Don't show account rows greyed out — an unreachable row is worse than an absent one.Don't split this into separate Sign up and Log in buttons — one entry point, and the screen behind it decides.Don't gate Explore or Add Project behind the menu — the render is free and stays free.
06 · Mobile chrome
Top bar and tab bar
The account control lives between two fixed bars, so both are specified here. Neither bar draws a simulated status bar — a mock phone clock is prototype furniture, not product UI.
390pt — top bar, and tab bar with the raised action
RoomPlans.ai
Projects
Explore
Messages
Settings
Why these numbers
56px top bar. Material's app-bar height, comfortably above iOS's 44pt floor. Set it with min-height and symmetric padding — never let a control define the bar, which is what makes it feel crowded.The account trigger matches desktop: a 38px avatar in a 48px target. It has to sit inside the bar with clearance above and below; at 48px it filled the bar edge to edge.The top bar reads Search, Message, Notification, right to left toward the avatar. Same 24–26px size and stroke-width 3 as the notification bell, so no icon reads heavier than the rest.Glyphs are 24px in full ink, top and bottom. These are filled paths with no stroke weight, so apparent thickness comes from colour — grey glyphs read as thinner, not quieter. Inactive tab labels carry the muted colour instead.The raised action is seated, not floating. 52px lifted 12px — roughly a quarter of the circle above the bar. Lifting it further (58px at 22px) reads as pasted on and puts its tap target partly over page content.The sheet must outrank the tab bar. It renders inside the sticky top bar, so its own z-index is scoped there — the top bar sits at 40 against the tab bar's 25, or the scrim appears behind the tabs.
Spec
Top bar min-height 56px · 0/20px padding · 18px gapTop bar icons Search, Message, Notification · 24–26px · stroke-width 3Account trigger 40px tall · 32px avatar · 16px chevronTab bar 8/8/14px padding · 5 equal columnsTab glyph / label 24px --ink-900 · 11px mediumRaised action 52px · margin-top -12px · 4px ringStacking top bar 40 · tab bar 25 · sheet 60